package nina.yiyou.attendance.s10merge.compute.offgain

import nina.yiyou.attendance.s10merge.compute.AttendDetailMerger
import spock.lang.Specification

import java.time.LocalDate
import java.time.LocalDateTime

class OffGainCalculatorTest extends Specification {

  List _curDay
  List _nextDay

  void setup() {
    // NOOP
  }

  def "Calc:普通下班"() {
    given:
    _curDay = [[2020, 1, 2], [9, 29], [+0, [18, 31]]]
    _nextDay = [[2020, 1, 3], [9, 30]]

    when:
    def result = calc()

    then:
    result == 0
  }

  def "Calc:加班过10点"() {
    given:
    _curDay = [[2020, 4, 17], [9, 19], [+0, [22, 00]]]
    _nextDay = [[2020, 4, 18], [10, 11]]

    when:
    def result = calc()

    then: // 制度去除了10点档
    result == 0
  }

  def "Calc:加班过12点"() {
    given:
    _curDay = [[2020, 3, 17], [9, 29], [+1, [1, 12]]]
    _nextDay = [[2020, 3, 18], [10, 00]]

    when:
    def result = calc()

    then:
    result == 3
  }

  def "Calc:加班过3点"() {
    given:
    _curDay = [[2021, 3, 17], [9, 29], [+1, [4, 42]]]
    _nextDay = [[2021, 3, 18], [10, 00]]

    when:
    def result = calc()

    then:
    result == 7.5d
  }

  def "Calc:加班过3点下午来"() {
    given:
    _curDay = [[2021, 3, 17], [9, 29], [+1, [4, 42]]]
    _nextDay = [[2021, 3, 18], [14, 00]]

    when:
    def result = calc()

    then:
    result == 4.5d
  }

  double calc() {
    def mockDay = {
      def stub = Stub(AttendDetailMerger.PunchDay)
      def d0 = _curDay[0] as List<Integer>
      def date = LocalDate.of(d0[0], d0[1], d0[2])
      stub.date() >> { date }

      def d1 = _curDay[1] as List<Integer>
      stub.punchIn() >> { date.atTime(d1[0], d1[1]) }

      def d2 = _curDay[2] as List
      def d21 = d2[1] as List<Integer>
      stub.punchOut() >> { date.plusDays((int) d2[0]).atTime(d21[0], d21[1]) }

      return stub
    }

    def mockNext = {
      def stub = Stub(OffGainCalculator.NextDay)
      def d0 = _nextDay[0] as List<Integer>
      def d1 = _nextDay[1] as List<Integer>
      stub.latePoint() >> { LocalDateTime.of(d0[0], d0[1], d0[2], d1[0], d1[1]) }
      return stub
    }

    return new OffGainCalculator(mockDay(), mockNext()).calc()
  }
}
